package com.edou.member.service.impl;

import java.util.Calendar;
import java.util.Date;
import java.util.List;
import java.util.Locale;

import javax.annotation.Resource;

import org.apache.commons.lang3.StringUtils;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.apache.ibatis.session.RowBounds;
import org.json.simple.JSONObject;
import org.json.simple.parser.JSONParser;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import com.edou.base.page.PageResult;
import com.edou.base.util.UUIDUtil;
import com.edou.member.dao.IMemberLoginTokenDao;
import com.edou.member.dao.IMemberUserDao;
import com.edou.member.dto.MemberLoginTokenCondition;
import com.edou.member.entity.MemberLoginToken;
import com.edou.member.entity.MemberUser;
import com.edou.member.form.MemberLoginTokenForm;
import com.edou.member.service.IMemberLoginTokenService;

import io.rong.ApiHttpClient;
import io.rong.models.FormatType;
import io.rong.models.SdkHttpResult;

/**
 * 会员APP端登录保存token表 
 * @creator     
 * @create-time 2016/6/17 17:37:46
 * @email admin@edou.com
 * @company www.edou.com
 * @version 1.0
 */
@Service("memberLoginTokenServiceImpl")
@Transactional(value = "transactionManager")
public class MemberLoginTokenServiceImpl implements IMemberLoginTokenService{
	
	private Log logger = LogFactory.getLog(MemberLoginTokenServiceImpl.class);
	
	@Value("${domain.path}")
	private String domainPath;
	/** 融云IM APP KEY */
	@Value("${rongim.appkey:#{null}}")
	private String rongimAppKey;
	/** 融云IM APP SECRECT */
	@Value("${rongim.appsecret:#{null}}")
	private String rongimAppSecrect;

	@Resource(name = "memberLoginTokenDaoImpl")
	private IMemberLoginTokenDao memberLoginTokenDao;
	@Resource(name = "memberUserDaoImpl")
	private IMemberUserDao memberUserDao;

	/**
	 * 查询所有会员APP端登录保存token表
	 */
	public List<MemberLoginToken> listMemberLoginTokenAll(){
		return memberLoginTokenDao.listMemberLoginTokenAll();
	}

	/**
	 * 分页查询
	 * @param pageResult 分页对象
	 * @param condition 查询条件类
	 */
	public void listMemberLoginTokenByPage(PageResult<MemberLoginToken> pageResult,MemberLoginTokenCondition condition){
		int rows = memberLoginTokenDao.listMemberLoginTokenByPageCount(condition);
		pageResult.setRows(rows);

		RowBounds rowBounds = new RowBounds(pageResult.getCurrentPageIndex(),pageResult.getPageSize());
		List<MemberLoginToken> list = memberLoginTokenDao.listMemberLoginTokenByPage(rowBounds,condition);
		pageResult.setResult(list);
	}

	/**
	 * 根据ID查询
	 * @param id 主键
	 * @return 会员APP端登录保存token表
	 */
	public MemberLoginToken getMemberLoginTokenById(Long id){
		return memberLoginTokenDao.getMemberLoginTokenById(id);
	}
	
	/**
	 * 根据会员ID获取会员登录信息
	 * @param memberId
	 * @return
	 */
	public MemberLoginToken getMemberLoginTokenByMemberId(String memberId){
		return memberLoginTokenDao.getMemberLoginTokenByMemberId(memberId);
	}

	@Override
	public MemberLoginToken getMemberLoginTokenByToken(String token) {
		return memberLoginTokenDao.getMemberLoginTokenByToken(token);
	}

	/**
	 * 新增
	 * @param item 会员APP端登录保存token表
	 */
	public void add(MemberLoginToken item){
		memberLoginTokenDao.add(item);
	}


	@Override
	public void updateExpireTime(MemberLoginToken item) {
		memberLoginTokenDao.updateExpireTime(item);
	}
	
	/**
	 * 更新在线状态
	 * @param item
	 */
	public void updateOnlineStatus(MemberLoginToken item){
		memberLoginTokenDao.updateOnlineStatus(item);
	}
	
	/**
	 * 将会员在线状态修改为离线
	 */
	public void updateMemberOfflineByLastAccessTime(){
		memberLoginTokenDao.updateMemberOfflineByLastAccessTime();
	}
	
	/**
	 * 保存会员登录token
	 * @param model
	 * @return
	 */
	public void saveMemberLoginToken(MemberLoginTokenForm model){
		//设置过期时间
		Date now = new Date();
		Calendar cal = Calendar.getInstance(Locale.CHINA);
		cal.setTime(now);
		cal.add(Calendar.DAY_OF_YEAR, 30);	//增加1个月
		Date expireTime = cal.getTime();
		
		String token = UUIDUtil.uuid() + UUIDUtil.uuid();	//生成64位随机数
		//2.判断当前会员是否已经登录
		MemberLoginToken memberLoginToken = memberLoginTokenDao.getMemberLoginTokenByMemberId(model.getMemberUser().getId());
		if(null != memberLoginToken){
			//删掉记录
			memberLoginTokenDao.delByIds(new Long[]{memberLoginToken.getId()});
		}
		
		//向融云服务器请求token
		String chatToken = null;
		if(StringUtils.isNotBlank(rongimAppKey) && StringUtils.isNotBlank(rongimAppSecrect)){
			try{
				SdkHttpResult result = ApiHttpClient.getToken(rongimAppKey, rongimAppSecrect, model.getMemberUser().getId(), model.getMemberUser().getNickName(),model.getMemberUser().getFacePath(), FormatType.json);
				logger.debug("获取融云IM聊天token数据服务器返回信息：" + result);
				if(null != result){
					JSONParser parser = new JSONParser();
					JSONObject json = (JSONObject) parser.parse(result.getResult());
					if(null != json && null != json.get("token")){
						chatToken = json.get("token").toString();
						logger.debug("获取到的融云IM聊天token：" + token);
					}
				}
			}catch(Exception ex){
				String msg = "获取融云IM聊天token失败：" + ex.getMessage();
				logger.error(msg,ex);
			}
			
		}
		
		
		//插入新数据
		memberLoginToken = new MemberLoginToken();
		memberLoginToken.setDeviceId(model.getDeviceId());
		memberLoginToken.setDeviceType(model.getDeviceType());
		memberLoginToken.setMemberId(model.getMemberUser().getId());
		memberLoginToken.setToken(token);	//生成token
		memberLoginToken.setExpireTime(expireTime);
		memberLoginToken.setChatToken(chatToken);
		memberLoginToken.setChatClientId(model.getChatClientId());
		memberLoginToken.setOnlineStatus(1);	//在线状态
		
		memberLoginTokenDao.add(memberLoginToken);
		
		model.setItem(memberLoginToken);
	}
	
	/**
	 * 仅登录，不涉及即时聊天工具
	 * @param model
	 * @return
	 */
	public MemberLoginToken simpleLoginToken(MemberUser member){
		//设置过期时间
		Date now = new Date();
		Calendar cal = Calendar.getInstance(Locale.CHINA);
		cal.setTime(now);
		cal.add(Calendar.DAY_OF_YEAR, 30);	//增加1个月
		Date expireTime = cal.getTime();
		
		String token = UUIDUtil.uuid() + UUIDUtil.uuid();	//生成64位随机数
		//2.判断当前会员是否已经登录
		MemberLoginToken memberLoginToken = memberLoginTokenDao.getMemberLoginTokenByMemberId(member.getId());
		if(null != memberLoginToken){
			//删掉记录 0628测试阶段暂时注释
			//memberLoginTokenDao.delByIds(new Long[]{memberLoginToken.getId()});
		}
		
		//插入新数据
		memberLoginToken = new MemberLoginToken();
		memberLoginToken.setDeviceId(member.getDeviceId());
		memberLoginToken.setDeviceType(member.getDeviceType());
		memberLoginToken.setMemberId(member.getId());
		memberLoginToken.setToken(token);	//生成token
		memberLoginToken.setExpireTime(expireTime);
		memberLoginToken.setOnlineStatus(1);	//在线状态
		
		memberLoginTokenDao.add(memberLoginToken);
		
		return memberLoginToken;
	}
	
	/**
	 * 第三方登录
	 * @param model
	 */
	public void thirdLogin(MemberLoginTokenForm model){
		MemberUser memberUser = memberUserDao.getMemberUserByAccount(model.getAccount());
		if(memberUser == null){
			memberUser = model.getMemberUser();
			memberUser.setCreateBy(model.getAccount());
			memberUser.setUpdateBy(model.getAccount());
			memberUser.setAccount(model.getAccount());
			memberUser.setName(model.getNickName());
			memberUser.setNickName(model.getNickName());
			if(StringUtils.isBlank(model.getFacePath())){
				//给默认图片
				String facePath = domainPath + "/static/mobile/base/images/head.png";
				memberUser.setFacePath(facePath);
			}else{
				memberUser.setFacePath(model.getFacePath());
			}
			
			memberUserDao.add(memberUser);
		}else{
			//更新头像
			if(StringUtils.isBlank(model.getFacePath())){
				//给默认图片
				String facePath = domainPath + "/static/mobile/base/images/head.png";
				memberUser.setFacePath(facePath);
			}else{
				memberUser.setFacePath(model.getFacePath());
			}
			memberUser.setUpdateBy(memberUser.getAccount());
			memberUserDao.updateFacePath(memberUser);
			
			model.setMemberUser(memberUser);
		}
		
		this.saveMemberLoginToken(model);
	}

	/**
	 * 根据ID集合批量删除
	 * @param ids ID集合
	 */
	public void delByIds(Long[] ids){
		memberLoginTokenDao.delByIds(ids);
	}
	
	/**
	 * 根据token删除
	 * @param token
	 */
	public void delByToken(String token){
		memberLoginTokenDao.delByToken(token);
	}
}

